package com.lagou.service;

import com.lagou.common.JSONSerializer;
import com.lagou.common.RpcDecoder;
import com.lagou.common.RpcRequest;
import com.lagou.handler.UserServerHandler;
import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.ChannelPipeline;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.SocketChannel;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import io.netty.handler.codec.string.StringEncoder;
import org.apache.curator.RetryPolicy;
import org.apache.curator.framework.CuratorFramework;
import org.apache.curator.framework.CuratorFrameworkFactory;
import org.apache.curator.retry.ExponentialBackoffRetry;
import org.apache.zookeeper.CreateMode;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import javax.annotation.PostConstruct;


@Service
public class UserServiceImpl implements UserService {

    @Value("${netty.port}")
    private String serverPort;

    private String ip = "127.0.0.1";

    private CuratorFramework client;

    public void startZkClient(){
        RetryPolicy retryPolicy = new ExponentialBackoffRetry(1000,3);
        client = CuratorFrameworkFactory.builder() .connectString("127.0.0.1:2181") //server地址
                .sessionTimeoutMs(5000) .connectionTimeoutMs(3000) .retryPolicy(retryPolicy) .namespace("netty-server") .build(); //
        client.start();
    }
    @PostConstruct
    public void init() throws Exception {
        this.startServer(ip,Integer.parseInt(serverPort));
        startZkClient();
        registerServer();
    }

    private void registerServer() throws Exception {
        client.create().creatingParentsIfNeeded().withMode(CreateMode.EPHEMERAL).forPath("/server-list/"+serverPort,(ip+":"+serverPort).getBytes());
    }

    public String sayHello(String word) {
        System.out.println("调用成功--参数 "+word);
        return "调用成功--参数 "+word;
    }

    //hostName:ip地址  port:端口号
    private void startServer(String hostName,int port) throws InterruptedException {

        NioEventLoopGroup bossGroup = new NioEventLoopGroup();
        NioEventLoopGroup workerGroup = new NioEventLoopGroup();

        ServerBootstrap serverBootstrap = new ServerBootstrap();
        serverBootstrap.group(bossGroup,workerGroup)
                .channel(NioServerSocketChannel.class)
                .childHandler(new ChannelInitializer<SocketChannel>() {
                    protected void initChannel(SocketChannel ch) throws Exception {
                        ChannelPipeline pipeline = ch.pipeline();
                        pipeline.addLast(new StringEncoder());
                        pipeline.addLast(new RpcDecoder(RpcRequest.class, new JSONSerializer()));
                        pipeline.addLast(new UserServerHandler());

                    }
                });
        serverBootstrap.bind(hostName,port).sync();

    }

}
